package com.quectel.cms.controller.partybuilding;


import com.quectel.cms.controller.BaseController;
import com.quectel.cms.vo.partybuilding.PartyOrganizationChangeVo;
import com.quectel.constant.global.SystemConstants;
import com.quectel.constant.global.TreeData;
import com.quectel.constant.global.annotation.RequirePermissions;
import com.quectel.core.module.partybuilding.dto.PartyOrganizationBuildingDto;
import com.quectel.core.module.partybuilding.dto.PartyOrganizationDto;
import com.quectel.core.module.partybuilding.dto.PartyOrganizationUnitDto;
import com.quectel.core.module.partybuilding.service.PartyOrganizationBuildingService;
import com.quectel.core.module.partybuilding.service.PartyOrganizationService;
import com.quectel.core.module.partybuilding.service.PartyOrganizationUnitService;
import com.quectel.core.module.really.dto.ReallyCompanyDto;
import com.quectel.core.module.really.service.ReallyCompanyService;
import com.quectel.core.module.village.dto.VillageBuildingDto;
import com.quectel.core.module.village.dto.VillageDto;
import com.quectel.core.module.village.service.VillageBuildingService;
import com.quectel.core.module.village.service.VillageService;
import com.quectel.util.common.Page;
import com.quectel.util.common.Request;
import com.quectel.util.common.Response;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.util.*;
import java.util.stream.Collectors;

/**
 *
 * @author bob
 * @email bob.yu@quectel.com
 * @date 2023/05/24 11:17
 */
@RestController
@RequestMapping("partyOrganization")
@Tag(name = "PartyOrganizationController", description = "党组织管理相关api")
public class PartyOrganizationController extends BaseController {

    @DubboReference
    private PartyOrganizationService partyOrganizationService;
    @DubboReference
    private VillageBuildingService villageBuildingService;
    @DubboReference
    private ReallyCompanyService reallyCompanyService;
    @DubboReference
    private PartyOrganizationUnitService partyOrganizationUnitService;
    @DubboReference
    private PartyOrganizationBuildingService partyOrganizationBuildingService;
    @DubboReference
    private VillageService villageService;

    /**
     * 变更党组织父级
     */
    @PostMapping("changeOrganization")
    @RequirePermissions(values = "partyOrganization:changeOrganization")
    @Operation(summary = "变更组织父级")
    public Response<Object> changeOrganization(
            @RequestBody PartyOrganizationChangeVo partyOrganizationChangeVo
    ) {

        PartyOrganizationDto organizationDto = partyOrganizationService.selectById(partyOrganizationChangeVo.getPartyOrganizationId());

        // 选中需要变更父id的组织
        PartyOrganizationDto shouldChangePartyOrganization = partyOrganizationService.selectById(partyOrganizationChangeVo.getShouldChangePartyOrganizationId());
        if (organizationDto!=null
                && shouldChangePartyOrganization!=null
                && !shouldChangePartyOrganization.getParentId().equals(SystemConstants.TREE_DEFAULT_PARENT_ID)
                && partyOrganizationChangeVo.getPartyOrganizationId().equals(partyOrganizationChangeVo.getPartyOrganizationId())
        ){
            PartyOrganizationDto updately = new PartyOrganizationDto();
            updately.setId(shouldChangePartyOrganization.getId());
            updately.setParentId(organizationDto.getId());
            partyOrganizationService.updateById(updately);
            return Response.ok();
        }else {
            return Response.error(SystemConstants.ILLEGAL_MSG);
        }
    }

    /**
     * 列表
     */
    @GetMapping("treeData")
    @RequirePermissions(values = "partyOrganization:list")
    @Operation(summary = "查询党组织树")
    public Response<List<TreeData>> treeData(
    ) {
        //查询列表数据
        Request request = Request.configParamsNotPage(Request.parseParams(httpServletRequest));
        super.fillAuthorityData(request.getParams());

        List<PartyOrganizationDto> depts = partyOrganizationService.queryList(request.getParams());

        List<TreeData> simpleTree = new ArrayList<>();

        simpleTree.addAll(
                depts.stream().map(v -> {
                    TreeData treeData = new TreeData();
                    treeData.setId(String.valueOf(v.getId()));
                    treeData.setName(v.getName());
                    treeData.setParentId(String.valueOf(v.getParentId()));
                    treeData.setOpen(SystemConstants.YES);
                    return treeData;
                }).collect(Collectors.toList())
        );
        if (simpleTree != null) {
            simpleTree.sort(new Comparator<TreeData>() {
                @Override
                public int compare(TreeData o1, TreeData o2) {
                    if (o1.getSort() != null && o2.getSort() != null) {
                        return o1.getSort() - o2.getSort();
                    }
                    return 0;
                }
            });
        }
        return Response.<List<TreeData>>ok().wrap(TreeData.simpleToChildren(simpleTree, SystemConstants.TREE_DEFAULT_PARENT_ID.toString()));
    }

    /**
     * 查询权限下所有党组织
     */
    @GetMapping("queryAll")
    @Operation(summary = "查询权限下所有党组织")
    public Response<List<PartyOrganizationDto>> queryAll() {

        Map<String, Object> params = Request.parseParams(httpServletRequest);
        super.fillAuthorityData(params);

        List<PartyOrganizationDto> list = partyOrganizationService.queryList(params);

        return Response.<List<PartyOrganizationDto>>ok().wrap(list);
    }

    /**
     * 查询权限下所有小区楼栋
     */
    @GetMapping("queryAllVillage")
    @Operation(summary = "查询权限下所有小区")
    public Response<List<VillageDto>> queryAllVillage() {
        Map<String, Object> params = Request.parseParams(httpServletRequest);
        super.fillAuthorityData(params);
        return Response.<List<VillageDto>>ok().wrap(villageService.queryList(params));
    }

    /**
     * 查询权限下所有小区楼栋
     */
    @GetMapping("queryAllBuilding")
    @Operation(summary = "查询权限下所有小区楼栋")
    public Response<Page<VillageBuildingDto>> queryAllBuilding() {
        Request request = Request.configParams(Request.parseParams(httpServletRequest));
        super.fillAuthorityData(request.getParams());

        int total = villageBuildingService.queryTotal(request.getParams());

        List<VillageBuildingDto> list = null;
        if (total > 0) {
            list = villageBuildingService.queryList(request.getParams());
        } else {
            list = new ArrayList<>();
        }

        Page<VillageBuildingDto> page = new Page<>(request.getPageNo(), request.getPageSize(), total, list);
        return Response.<Page<VillageBuildingDto>>ok().wrap(page);
    }

    /**
     * 查询权限下所有单位
     */
    @GetMapping("queryAllCompany")
    @Operation(summary = "查询权限下所有单位")
    public Response<List<ReallyCompanyDto>> queryAllCompany() {
        Map<String, Object> params = Request.parseParams(httpServletRequest);
        super.fillAuthorityData(params);
        return Response.<List<ReallyCompanyDto>>ok().wrap(reallyCompanyService.queryList(params));
    }

    /**
     * 分页查询
     *
     * @param pageNo
     * @param pageSize
     * @return
     */
    @GetMapping("list")
    @RequirePermissions(values = "partyOrganization:list")
    @Operation(summary = "分页获取党组织管理列表")
    public Response<Page<PartyOrganizationDto>> list(
            @Parameter(description = "从1开始的页码数") @RequestParam Integer pageNo,
            @Parameter(description = "每页多少条") @RequestParam Integer pageSize
    ) {
        //查询列表数据
        Request request = Request.configParams(Request.parseParams(httpServletRequest));

        Long id = request.getLong("id");

        List<PartyOrganizationDto> recursion =partyOrganizationService.recursion(id);

        request.getParams().put(SystemConstants.ENTITY_ID_COLLECTION_FLAG, recursion.stream().map(PartyOrganizationDto::getId).toArray(Long[]::new));

        super.fillAuthorityData(request.getParams());
        int total = partyOrganizationService.queryTotal(request.getParams());

        List<PartyOrganizationDto> list = null;
        if (total > 0) {
            list = partyOrganizationService.queryList(request.getParams());
        } else {
            list = new ArrayList<>();
        }

        Page<PartyOrganizationDto> page = new Page<>(request.getPageNo(), request.getPageSize(), total, list);
        return Response.<Page<PartyOrganizationDto>>ok().wrap(page);
    }

    /**
     * 编辑查询反显
     *
     * @param id
     * @return
     */
    @GetMapping("infoForEdit/{id}")
    @RequirePermissions(values = "partyOrganization:edit")
    @Operation(summary = "在编辑时根据id查询党组织管理详情")
    public Response<PartyOrganizationDto> infoForEdit(@PathVariable("id") Long id) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        PartyOrganizationDto partyOrganizationDto = partyOrganizationService.selectById(id);

        // 填充单位信息
        List<ReallyCompanyDto> unitDtoList = new ArrayList<>();
        List<PartyOrganizationUnitDto> unitBindingDtos = partyOrganizationUnitService.selectList(partyOrganizationDto.getTenantId(),id);
        if (CollectionUtils.isNotEmpty(unitBindingDtos)) {
            for (PartyOrganizationUnitDto binding : unitBindingDtos) {
                ReallyCompanyDto companyDto = reallyCompanyService.selectCacheById(binding.getUnitId());
                if (companyDto != null) {
                    unitDtoList.add(companyDto);
                }
            }
        }
        partyOrganizationDto.setCompanyList(unitDtoList);

        // 填充楼栋信息
        List<VillageBuildingDto> buildingDtoList = new ArrayList<>();
        List<PartyOrganizationBuildingDto> partyOrganizationBuildingDtos = partyOrganizationBuildingService.selectList(partyOrganizationDto.getTenantId(),id);
        if (CollectionUtils.isNotEmpty(partyOrganizationBuildingDtos)){
            for (PartyOrganizationBuildingDto binding : partyOrganizationBuildingDtos) {
                VillageBuildingDto villageBuildingDto = villageBuildingService.selectById(binding.getBuildingId());
                if (villageBuildingDto != null){
                    buildingDtoList.add(villageBuildingDto);
                }
            }
        }
        partyOrganizationDto.setVillageBuildingList(buildingDtoList);

        return Response.<PartyOrganizationDto>ok().wrap(partyOrganizationDto);
    }

    /**
     * 详情
     *
     * @param id
     * @return
     */
    @GetMapping("info/{id}")
    @RequirePermissions(values = "partyOrganization:info")
    @Operation(summary = "根据id查询党组织管理的详情")
    public Response<PartyOrganizationDto> info(@PathVariable("id") Long id) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        PartyOrganizationDto partyOrganizationDto = partyOrganizationService.selectById(id);

        return Response.<PartyOrganizationDto>ok().wrap(partyOrganizationDto);
    }

    /**
     * 保存
     *
     * @param partyOrganizationDto
     * @return
     */
    @PostMapping("save")
    @RequirePermissions(values = "partyOrganization:edit")
    @Operation(summary = "新增党组织管理")
    public Response<Object> save(@RequestBody @Validated PartyOrganizationDto partyOrganizationDto) {

        //填充基础数据
        fillSaveCommonData(partyOrganizationDto);

        if (CollectionUtils.isEmpty(partyOrganizationDto.getVillageBuildingList())){
            return Response.error("党组织绑定楼栋资源不能为空");
        }
        partyOrganizationService.saveOrUpdate(partyOrganizationDto);

        return Response.ok();
    }


    /**
     * 修改
     *
     * @param partyOrganizationDto
     * @return
     */
    @PostMapping("update")
    @RequirePermissions(values = "partyOrganization:edit")
    @Operation(summary = "根据id修改党组织管理")
    public Response<Object> update(@RequestBody  @Validated PartyOrganizationDto partyOrganizationDto) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        //填充基础数据
        fillEditCommonData(partyOrganizationDto);

        if (CollectionUtils.isEmpty(partyOrganizationDto.getVillageBuildingList())){
            return Response.error("党组织绑定楼栋资源不能为空");
        }

        partyOrganizationService.saveOrUpdate(partyOrganizationDto);

        return Response.ok();
    }

    /**
     * 批量删除
     *
     * @param ids
     * @return
     */
    @PostMapping("delete")
    @RequirePermissions(values = "partyOrganization:delete")
    @Operation(summary = "根据多条记录id批量删除党组织管理")
    public Response<Object> delete(@RequestBody Long[] ids) {

        Map<String, Object> params = new HashMap<>();
        super.fillAuthorityData(params);

        for (Long id : ids) {
            PartyOrganizationDto organizationDto = partyOrganizationService.selectById(id);
            // 根节点不允许删除
            if ( SystemConstants.TREE_DEFAULT_PARENT_ID.equals(organizationDto.getParentId())){
                return Response.error("树根节点不允许删除");
            }

        }

        partyOrganizationService.deleteBatch(ids);

        return Response.ok();
    }
}
